In [1]:
import json
import folium
from folium.plugins import MarkerCluster
import pandas as pd
from IPython.display import display, Math, Latex
In [2]:
# read some data
crime = pd.read_csv("WestLA_Crime_2020.csv")
crime_type1 = crime[crime["Crm Cd Desc"] == "BIKE - STOLEN"][["DATE OCC", "LAT", "LON", "Vict Age", "Vict Sex", "Vict Descent"]]
crime_type1
Out[2]:
DATE OCC LAT LON Vict Age Vict Sex Vict Descent
34 01/01/2020 12:00:00 AM 34.0389 -118.4226 31 F W
175 01/08/2020 12:00:00 AM 34.0412 -118.3813 23 M W
216 01/09/2020 12:00:00 AM 34.0351 -118.3830 30 M H
228 01/10/2020 12:00:00 AM 34.0313 -118.4536 55 M W
247 01/10/2020 12:00:00 AM 34.0406 -118.4518 23 M O
... ... ... ... ... ... ...
32055 03/29/2023 12:00:00 AM 34.0519 -118.4319 29 M Z
32111 03/31/2023 12:00:00 AM 34.0609 -118.3814 24 F W
32413 04/14/2023 12:00:00 AM 34.0341 -118.4525 51 M H
32420 04/14/2023 12:00:00 AM 34.0566 -118.4445 22 M C
32523 04/19/2023 12:00:00 AM 34.0562 -118.4423 27 F W

960 rows × 6 columns

In [3]:
# Define coordinates of where we want to center our map
ucla_coords = [34.07124, -118.44115]

#Create the map
my_map = folium.Map(location = ucla_coords, zoom_start = 15)
In [4]:
# Display the map

for idx, row in crime_type1.iterrows():
    folium.Marker(location=[row['LAT'], row['LON']], 
                  popup = (f"Gender and Age are: {row['Vict Sex']}, \
                           {row['Vict Age']}")).add_to(my_map)

my_map
Out[4]:
Make this Notebook Trusted to load map: File -> Trust Notebook
In [5]:
df = pd.read_csv('All_Starbucks_Locations_in_the_World.csv')
df['text'] = df['Name'] + '' + df['Country Subdivision'].astype(str)

SB = df[df['Country Subdivision']=='CA'][['text', 'Latitude', 'Longitude']].dropna()
In [6]:
for idx, row in SB.iterrows():
    folium.CircleMarker(
        location=[row['Latitude'],row['Longitude']],
        radius=10,
        fill_color='white',
        fill=True,
        fill_opacity=1,
        color='#00704A',
        popup = (f"{row['text']}")
    ).add_to(my_map)
    
In [7]:
my_map
Out[7]:
Make this Notebook Trusted to load map: File -> Trust Notebook
In [8]:
df = pd.read_csv('Private_and_Charter_Schools.csv')[['X','Y',
        'Name', 'addrln1', 'city', 'zip']]
df['text'] = df['Name'] + '\n' + df['addrln1'] + '\n' \
+ df['city']+ '\n' + df['zip'].astype(str)
In [9]:
# Define coordinates of where we want to center our map
la_coords = [34.06258325620414, -118.25912552934548]

#Create the map
my_map2 = folium.Map(location = la_coords, zoom_start = 12)
In [10]:
# Display the map

for idx, row in df.iterrows():
    folium.CircleMarker(
        location=[row['Y'], row['X']],
        radius=3,
        fill=True,
        color='cyan',
        popup = (f"School: {row['text']}")
    ).add_to(my_map2)

my_map2
Out[10]:
Make this Notebook Trusted to load map: File -> Trust Notebook

Adding lines to maps¶

  • We could connect points (not demonstrated)
  • We can also find existing datasets with lines
  • Folium can use it directly

https://geohub.lacity.org/datasets/lacounty::fault-trace/explore?location=34.308942%2C-118.315582%2C9.81

In [11]:
%%script false --no-raise-error
{
"type": "FeatureCollection",
"name": "Fault_Trace",
"crs": { "type": "name", "properties": { "name": "urn:ogc:def:crs:OGC:1.3:CRS84" } },
"features": [
{ "type": "Feature", "properties": { "OBJECTID": 2496, "BLANK": null, "line": null,
                                    "FAULT_TYPE": "Accurately Located Fault Traces",
                                    "CA_MAP_LEGEND": "Solid lines (accurately located fault traces)",
                                    "FAULT_NAME": "Tujunga Fault", "FAULT_ZONE": "Sierra Madre Fault Zone",
                                    "LINE_TYPE": "Accurately Located", "LINE_STYLE": "Solid Line",
                                    "COMMENTS": " ", "QUAD_NAME": "San Fernando",
                                    "Shapelen": 163.50894307148619 },
 "geometry": { "type": "LineString", 
              "coordinates": [ [ -118.376765451005397, 34.284961232387367 ],
                              [ -118.377096157550085, 34.284994324363787 ],
                              [ -118.377302642146319, 34.28501642875851 ] ] } },
{ "type": "Feature", "properties": { "OBJECTID": 2497, "BLANK": null, "line": null, "FAULT_TYPE": "Accurately Located Fault Traces", "CA_MAP_LEGEND": "Solid lines (accurately located fault traces)", "FAULT_NAME": "Kagel Fault", "FAULT_ZONE": "Sierra Madre Fault Zone", "LINE_TYPE": "Accurately Located", "LINE_STYLE": "Solid Line", "COMMENTS": " ", "QUAD_NAME": "Sunland", "Shapelen": 284.31634686360053 }, "geometry": { "type": "LineString", "coordinates": [ [ -118.374609104068895, 34.291648769979808 ], [ -118.374459214542668, 34.291645677869106 ], [ -118.374259658503092, 34.291644161692787 ], [ -118.374161194108524, 34.291650151026161 ], [ -118.37400115872984, 34.291676233648943 ], [ -118.373683755147013, 34.291751133979943 ] ] } },
In [12]:
faults = 'Fault_Trace.geojson'

my_map3 = folium.Map(location = ucla_coords, zoom_start = 13)
folium.GeoJson(faults, name='geojson').add_to(my_map3)

my_map3
Out[12]:
Make this Notebook Trusted to load map: File -> Trust Notebook

Adding polygons¶

  • We can also find existing datasets of shapes
  • Folium can use the data directly

https://geohub.lacity.org/datasets/lahub::lapd-divisions/explore?location=34.019778%2C-118.410104%2C10.66

In [13]:
divisions = 'LAPD_divisions.geojson'

my_map4 = folium.Map(location = la_coords, zoom_start = 12)
folium.GeoJson(divisions, name='geojson').add_to(my_map4)

my_map4
Out[13]:
Make this Notebook Trusted to load map: File -> Trust Notebook
In [14]:
folium.GeoJson(divisions, name='geojson').add_to(my_map2)
my_map2
Out[14]:
Make this Notebook Trusted to load map: File -> Trust Notebook

Choropleth in Folium¶

  • As in plotly, we can build choropleth maps
  • Create a map object
  • Generate boundaries
  • Add data
In [15]:
# initialize the map and store it in a m object
m = folium.Map(location=[40, -95], zoom_start=4)
m
Out[15]:
Make this Notebook Trusted to load map: File -> Trust Notebook
In [16]:
# Open the file
with open('geojson-counties-fips.json', 'r') as f:
    # Load the JSON data from the file
    counties = json.load(f)   
In [17]:
counties['features'][0]['id']
Out[17]:
'01001'
In [18]:
pov = pd.read_csv('PovertyEstimates.csv', 
                  dtype={'id': str})
pov
Out[18]:
id Stabr Area_name Urban_Code PCTPOVALL_2020
0 01001 AL Autauga County 2 11.2
1 01003 AL Baldwin County 3 8.9
2 01005 AL Barbour County 6 25.5
3 01007 AL Bibb County 1 17.8
4 01009 AL Blount County 1 13.1
... ... ... ... ... ...
3136 56037 WY Sweetwater County 5 7.6
3137 56039 WY Teton County 7 5.2
3138 56041 WY Uinta County 7 8.5
3139 56043 WY Washakie County 7 9.7
3140 56045 WY Weston County 7 10.6

3141 rows × 5 columns

In [19]:
folium.Choropleth(
    geo_data=counties,
    name="choropleth",
    data=pov,
    columns=["id", "PCTPOVALL_2020"],
    key_on="id",
    legend_name="Poverty Rate (%)",
).add_to(m)


m
Out[19]:
Make this Notebook Trusted to load map: File -> Trust Notebook